package com.idanchuang.support.etcache.pubsub.amqp;

import com.idanchuang.support.etcache.ConditionalOnEtCacheEnabled;
import com.idanchuang.support.etcache.pubsub.RemoteEventPublisher;
import com.idanchuang.support.etcache.pubsub.RemoteEventSubscriber;
import com.idanchuang.support.etcache.pubsub.SubEventQueue;
import com.idanchuang.support.etcache.remote.codec.RemoteKeyCodec;
import com.rabbitmq.client.ConnectionFactory;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.boot.autoconfigure.condition.ConditionalOnClass;
import org.springframework.boot.autoconfigure.condition.ConditionalOnMissingBean;
import org.springframework.boot.autoconfigure.condition.ConditionalOnProperty;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;

/**
 * @author yjy
 * Created at 2022/3/28 5:08 下午
 */
@Configuration
@ConditionalOnEtCacheEnabled
@ConditionalOnClass(ConnectionFactory.class)
@ConditionalOnProperty(prefix = "idanchuang.component.etcache", name = "eventType", havingValue = "amqp")
public class AmqpRemoteEventAutoConfiguration {

    @Value("${spring.application.name}")
    private String appId;
    @Value("${spring.rabbitmq.addresses:}")
    private String addresses;
    @Value("${spring.rabbitmq.host:localhost}")
    private String host;
    @Value("${spring.rabbitmq.username:guest}")
    private String username;
    @Value("${spring.rabbitmq.password:guest}")
    private String password;
    @Value("${spring.rabbitmq.port:5672}")
    private int port;
    @Value("${spring.rabbitmq.virtualHost:${spring.rabbitmq.virtual-host:/}}")
    private String virtualHost;
    @Value("${spring.rabbitmq.useNio:false}")
    private boolean useNio;

    @Bean
    @ConditionalOnMissingBean(ConnectionFactory.class)
    public ConnectionFactory etCacheAmqpConnectionFactory() {
        ConnectionFactory connectionFactory = new ConnectionFactory();
        if (!"".equals(this.addresses)) {
            String adr = this.addresses.split(",")[0];
            connectionFactory.setHost(adr.split(":")[0]);
            connectionFactory.setPort(Integer.parseInt(adr.split(":")[1]));
        } else {
            connectionFactory.setHost(this.host);
            connectionFactory.setPort(this.port);
        }
        connectionFactory.setUsername(this.username);
        connectionFactory.setPassword(this.password);
        connectionFactory.setVirtualHost(this.virtualHost);
        if (useNio) {
            connectionFactory.useNio();
        }
        return connectionFactory;
    }

    @Bean
    @ConditionalOnMissingBean(RemoteEventSubscriber.class)
    public RemoteEventSubscriber remoteEventSubscriber(RemoteKeyCodec remoteKeyCodec,
                                                              SubEventQueue subEventQueue,
                                                              ConnectionFactory connectionFactory) {
        return new AmqpRemoteEventSubscriber(remoteKeyCodec, subEventQueue, appId.toLowerCase(), connectionFactory);
    }

    @Bean
    @ConditionalOnMissingBean(RemoteEventPublisher.class)
    public RemoteEventPublisher remoteEventPublisher(ConnectionFactory connectionFactory) {
        return new AmqpRemoteEventPublisher(appId.toLowerCase(), connectionFactory);
    }

}
